package cn.edu.xaut.mybatisers.mall.tool;

import cn.edu.xaut.mybatisers.mall.Exception.ExceptionEntity.LoginException;
import org.springframework.stereotype.Component;

import javax.crypto.*;
import java.security.GeneralSecurityException;
import java.security.InvalidKeyException;
import java.security.NoSuchAlgorithmException;
import java.security.Security;
import java.time.LocalDateTime;
import java.time.format.DateTimeFormatter;

@Component
public class LoginStatus {
    final String alphabet = "ABCDEFGHIZKLMNOPQRSTUVWXYZ";
    final String flag = "!@#$%^&*()_+/*-+{}|:";
    DateTimeFormatter ofPattern = DateTimeFormatter.ofPattern("yyyyMMddHHmmss");
    private KeyGenerator keygen;
    private SecretKey deskey;
    private Cipher c;

    public LoginStatus() throws NoSuchAlgorithmException, NoSuchPaddingException {
        Security.addProvider(new com.sun.crypto.provider.SunJCE());
        keygen = KeyGenerator.getInstance("DES");
        deskey = keygen.generateKey();
        c = Cipher.getInstance("DES");
    }

    public  String generateLoginStatus(int customer_id) throws InvalidKeyException, IllegalBlockSizeException, BadPaddingException {
        String str_id = String.valueOf(customer_id), str;
        LocalDateTime now = LocalDateTime.now().plusHours(1);
        String localDate = now.format(ofPattern);
        if(str_id.length() >= 5){
            str = str_id.substring(str_id.length() - 5, str_id.length());
        }else {
            str = String.format("%0" + 5 + "d", customer_id);
        }
        // 5位custom_id + 14位时间
        str = str + localDate;
        byte[] src = str.getBytes();
        c.init(Cipher.ENCRYPT_MODE, deskey);
        byte[] result_byte = c.doFinal(src);

        return byteToString(result_byte);
    }

    public  Boolean checkLoginStatus(String token) throws InvalidKeyException, LoginException {
        byte[] bytes = StringToByte(token);
        c.init(Cipher.DECRYPT_MODE, deskey);
        String str = null;
        try {
            str = new String(c.doFinal(bytes));
        } catch (GeneralSecurityException e) {
            throw new LoginException("登录态不完整");
        }

        String dueTime_str = str.substring(5);
        LocalDateTime dueTime = LocalDateTime.parse(dueTime_str, ofPattern);
        return dueTime.isAfter(LocalDateTime.now());
    }

    public String byteToString(byte[] bytes){
        StringBuilder str = new StringBuilder();
        int a, x, z;

        for (byte b : bytes){
            a = (int)b;
            x = a % 24;
            z = a / 24;
            if (a > 0){
                str.append(String.valueOf((int) (Math.random() * 10))).append(alphabet.charAt(z)).append(alphabet.charAt(x));
            }else {
                str.append(flag.charAt((int) (Math.random() * 20))).append(alphabet.charAt(-z)).append(alphabet.charAt(-x));
            }
        }
        return str.toString();
    }

    public byte[] StringToByte(String str){
        int total = str.length() / 3, j=0;
        byte[] bytes = new byte[total];

        for (int i=0; i<total; i++){
             String token = str.substring(3*i, 3*(i+1));
             int num = (flag.indexOf(token.charAt(0))== -1 ? -1 : 1) * (-1) *
                     (alphabet.indexOf(token.charAt(1))*24 + alphabet.indexOf(token.charAt(2)));
             bytes[j++] = (byte)num;
        }

        return bytes;
    }

}
